﻿using GalaSoft.MvvmLight;
using System.Collections.ObjectModel;
using System.Windows.Input;
using System;
using System.Collections.Generic;
using HouseKeepingPL.HKService;
using GalaSoft.MvvmLight.Messaging;
using GalaSoft.MvvmLight.Command;

namespace HouseKeepingPL.ViewModel
{
    /// <summary>
    /// This class contains properties that a View can data bind to.
    /// <para>
    /// Use the <strong>mvvminpc</strong> snippet to add bindable properties to this ViewModel.
    /// </para>
    /// <para>
    /// You can also use Blend to data bind with the tool's support.
    /// </para>
    /// <para>
    /// See http://www.galasoft.ch/mvvm/getstarted
    /// </para>
    /// </summary>
    public class ReportViewModel : ViewModelBase
    {
        #region privates
        private User _currentUser = null;
        private ObservableCollection<ReportType> _reportTypes; // report types from db (init on startup)
        ReportMessage reportMessage = null;

        #endregion
        /// <summary>
        /// Initializes a new instance of the ReportViewModel class.
        /// </summary>
        /// 
        public ReportViewModel()
        {
            #region messages registrations
            Messenger.Default.Register<ObservableCollection<ReportType>>(this, GetReportTypeList);
            Messenger.Default.Register<User>(this, GetUser);
            Messenger.Default.Register<ReportMsgs>(this, GetTextMessage);
            #endregion

            #region relay commands
            // report relay commands
            GetIncomeReportCommand = new RelayCommand(() => GetIncomeReportCommandExcecute(), () => true);
            GetOutcomeReportCommand = new RelayCommand(() => GetOutcomeReportCommandExcecute(), () => true);
            GetBalanceReportCommand = new RelayCommand(() => GetBalanceReportCommandExcecute(), () => true);

            // more reports relay commands
            GetIncomeReportBySectionsCommand = new RelayCommand(() => GetIncomeReportBySectionsCommandExcecute(), () => true);
            GetOutcomeReportBySectionsCommand = new RelayCommand(() => GetOutcomeReportBySectionsCommandExcecute(), () => true);
            #endregion
        }

        #region messages actions
        /// <summary>
        /// gets report types from sender
        /// </summary>
        /// <param name="list"></param>
        private void GetReportTypeList(ObservableCollection<ReportType> list)
        {
            ReportTypes = list;
            RaisePropertyChanged("ReportTypes");
        }

        /// <summary>
        /// get current user from sender
        /// </summary>
        /// <param name="user"></param>
        private void GetUser(User user)
        {
            _currentUser = user;
            reportMessage = new ReportMessage();
            if (_currentUser != null)
            {
                reportMessage.Username = _currentUser.Username;
            }
            else
            {
                reportMessage.Username = string.Empty;
            }

        }

        /// <summary>
        /// get action "what to do"
        /// </summary>
        /// <param name="msg"></param>
        private void GetTextMessage(ReportMsgs msg)
        {
            if (msg == ReportMsgs.InitSession)
            {
                TotalReportText = String.Empty; // Clean report between users
                DateFrom = DateTime.Now.AddMonths(-1); // init date from 
                DateTo = DateTime.Now;                 // init date to
                CurrentlySelectedReportTypeId = 1;
            }

            if (msg == ReportMsgs.RefreshReports)
            {
                CmdGetReportExcecute(CurrentlySelectedReportTypeId);
            }
        }
        #endregion

        #region Reports

        #region Report commands
        public ICommand GetIncomeReportCommand { get; private set; }
        public ICommand GetOutcomeReportCommand { get; private set; }
        public ICommand GetBalanceReportCommand { get; private set; }
        public ICommand GetIncomeReportBySectionsCommand { get; private set; }
        public ICommand GetOutcomeReportBySectionsCommand { get; private set; }
        #endregion

        #region reports actions
        private void GetIncomeReportCommandExcecute()
        {
            
            reportMessage.DateFrom = DateFrom;
            reportMessage.DateTo = DateTo;

            Double total = ClientProxy.Proxy.GetTotalIncomeForPeriod(reportMessage);
            ReportChartItems.Clear();
            ReportChartItems.Add(new KeyValuePair<string, decimal>("Income", (decimal)total));
            TotalReportText = "Your total Income is:\n " + total.ToString();
        }
        private void GetOutcomeReportCommandExcecute()
        {         
            reportMessage.DateFrom = DateFrom;
            reportMessage.DateTo = DateTo;

            Double total = ClientProxy.Proxy.GetTotalOutcomeForPeriod(reportMessage);
            ReportChartItems.Clear();
            ReportChartItems.Add(new KeyValuePair<string, decimal>("Outcome", (decimal)total));
            TotalReportText = "Your total Outccome is:\n " + total.ToString();
        }
        private void GetBalanceReportCommandExcecute()
        {
            reportMessage.DateFrom = DateFrom;
            reportMessage.DateTo = DateTo;

            double total = ClientProxy.Proxy.GetTotalBalanceForPeriod(reportMessage);
            ReportChartItems.Clear();
            ReportChartItems.Add(new KeyValuePair<string, decimal>("Balance", (decimal)total));
            TotalReportText = "Your total Balance is:\n " + total.ToString();
        }
        private void GetIncomeReportBySectionsCommandExcecute()
        {
            reportMessage.DateFrom = DateFrom;
            reportMessage.DateTo = DateTo;

            var total = ClientProxy.Proxy.GetIncomesBySections(reportMessage);
            TotalReportText = String.Empty;
            ReportChartItems.Clear();

            foreach (Report item in total) // stackpile all of the data for the report
            {
                ReportChartItems.Add(new KeyValuePair<string, decimal>(item.AType, item.SumOfAmount));
                TotalReportText += String.Format("{0} - {1} \n", item.AType, item.SumOfAmount);
            }

        }
        private void GetOutcomeReportBySectionsCommandExcecute()
        {
            reportMessage.DateFrom = DateFrom;
            reportMessage.DateTo = DateTo;

            var total = ClientProxy.Proxy.GetOutcomesBySections(reportMessage);
            TotalReportText = String.Empty;
            ReportChartItems.Clear();

            foreach (Report item in total) // stackpile all of the data for the report
            {
                ReportChartItems.Add(new KeyValuePair<string, decimal>(item.AType, item.SumOfAmount));
                TotalReportText += String.Format("{0} - {1} \n", item.AType, item.SumOfAmount);
            }
        }
        private void CmdGetReportExcecute(int ReportID)
        {
            switch (ReportID)
            {
                case 1:
                    GetIncomeReportCommandExcecute();
                    break;
                case 2:
                    GetOutcomeReportCommandExcecute();
                    break;
                case 3:
                    GetBalanceReportCommandExcecute();
                    break;
                case 4:
                    GetIncomeReportBySectionsCommandExcecute();
                    break;
                case 5:
                    GetOutcomeReportBySectionsCommandExcecute();
                    break;
                default:
                    break;
            }
        }
        #endregion

        #region binding
        private string _totalReportText;
        public string TotalReportText
        {
            get { return _totalReportText; }
            set
            {
                _totalReportText = value;
                RaisePropertyChanged("TotalReportText");
            }
        }

        private DateTime _DateFrom;

        public DateTime DateFrom
        {
            get
            {
                return _DateFrom;
            }
            set
            {
                _DateFrom = value;
                CmdGetReportExcecute(CurrentlySelectedReportTypeId);
                RaisePropertyChanged("DateFrom");
            }
        }

        private DateTime _DateTo;

        public DateTime DateTo
        {
            get
            {
                return _DateTo;
            }
            set
            {
                _DateTo = value;
                CmdGetReportExcecute(CurrentlySelectedReportTypeId);
                RaisePropertyChanged("DateTo");
            }
        }

        public ObservableCollection<ReportType> ReportTypes
        {
            get
            {
                return _reportTypes;
            }
            set
            {
                _reportTypes = value;
                RaisePropertyChanged("ReportTypes");
            }
        }

        private int _reportTypeId;

        public int CurrentlySelectedReportTypeId
        {
            get { return _reportTypeId; }
            set
            {
                _reportTypeId = value;
                CmdGetReportExcecute(_reportTypeId);
                RaisePropertyChanged("CurrentlySelectedReportTypeId");
            }
        }



        #endregion

        #region chart
        private ObservableCollection<KeyValuePair<string, Decimal>> _reportChartItems = new ObservableCollection<KeyValuePair<string, decimal>>();

        public ObservableCollection<KeyValuePair<string, Decimal>> ReportChartItems
        {
            get
            {
                return _reportChartItems;
            }
            set
            {
                _reportChartItems = value;
                RaisePropertyChanged("ReportChartItems");
            }
        }
        #endregion

        #endregion

    }
}